#pragma once

#include "IGameState.h"
#include "Entity.h"
#include "IEvent.h"
#include "System.h"
#include "CameraNode.h"
#include "GUITextbox.h"
#include "GUIComboBox.h"
#include "GUIWindow.h"
#include "GUIListBox.h"
#include "GUIButton.h"
#include "GUIMenu.h"
#include "GUITree.h"
#include "LightNode.h"
#include "Library.h"
#include "Waypoint.h"
#include "ITask.h"

class EditorGameState
{
	// Interface Functions
public:
	EditorGameState( Pointer<CameraNode>& cameraNode );
	// Button Function
	void CreateEntity();
	void CreateWaypointComponent();
	void SetPosition();
	void ShowLoadModelWindow();
	void CancelLoadModel();
	void LoadModel();
	void DisplayLoadTexture();
	void CancelLoadTexture();
	void LoadTexture();
	void SetGraphic();
	void AddRigidbodyShape();
	void ShowRigidBodyShapes();
	void DeleteRigidBodyShape();
	void HideRigidBodyShapes();
	void DeleteAllRigidBodyShapes();
	void ShowCreateTerrainWindow();
	void CreateTerrain();
	void CancelCreateTerrain();
	void DisplaySceneGraph();
	void CloseSceneGraph();
	void DeleteSceneGraphNode();
	void CreateLight();
	void OnSceneNodeChangeSelected();
	void SetLightPosition();
	void DisplayUnloadState();
	void UnloadState();
	void CancelUnloadState();
	void DisplayLoadState();
	void LoadState();
	void CancelLoadState();
	void SetEntityName();
	void DisplayEntityNames();
	void DeleteEntityByName();
	void HideEntityWindow();
	void OnEntityListSelectedChange();
	void DisplayCreateWaypoint();
	void CancelCreateWaypoint();
	void SetWaypointRadius();
	void DeletePathfinder();
	void CreatePathfinderComponent();
	void DisplayCreatePathfinder();
	void CancelCreatePathfinder();
	void CreateMenuItemsForNodeVector(GUITreeNode::Vector_t& children, INode::Vector_t& nodes);
	void Run();
	void Stop();
	void EnterRunningGameState();
	void ExitRunningGameState();

	// Game State Functions
	void RegisterEntity( HashedString id, Pointer<Entity>& entity );
	void RemoveEntity( HashedString id );
	Pointer<Entity> RetrieveEntity( HashedString id ) const;
	bool ReceiveEvent( IEvent& event );
	void setTimer( Pointer<ITask>& timer );
	void setPhysics( Pointer<ITask>& physics );

	bool UnloadNode( INode* node, tinyxml2::XMLPrinter& printer );
	bool UnloadComponent( const IComponent::Pair_t& componentPair, tinyxml2::XMLPrinter& printer );
	bool UnloadResource( const Library::ResourcesPair_t& resource, tinyxml2::XMLPrinter& printer);
	bool UnloadEntity( const Entity::Pair_t& entityPair, tinyxml2::XMLPrinter& printer );
	bool UnloadGameState( std::string filename );
	bool LoadState( std::string filename );
	bool LoadResources(tinyxml2::XMLElement* element);
	bool LoadModel(tinyxml2::XMLElement* element);
	bool LoadResource(tinyxml2::XMLElement* element);
	bool LoadEntities(tinyxml2::XMLElement* element);
	bool LoadEntity(tinyxml2::XMLElement* element);
	bool LoadNode(INode* workingNode, tinyxml2::XMLElement* element);
	bool LoadSceneGraph(tinyxml2::XMLElement* element);
	
	void SelectEntity( int x, int y );
	void ChangeSelected( Entity* selected );
	void DisplayLightProperties( Pointer<LightNode>& light );
	void DragDropSceneGraph();

	void LoadTexture(std::string fileName);
	bool FindWaypointGroup( HashedString& group, Pointer<Pathing::Waypoint>& waypoint );
	void RegisterWaypoint( HashedString& group, Pointer<Pathing::Waypoint>& waypoint );
private:
	Pointer<CameraNode> m_cameraNode;
	Pointer<System> m_selectables;
	Pathing::Waypoint::GroupMap_t m_waypoints;
	unsigned int m_entityCounter;
	std::vector<std::string> m_textureStrings;
	Entity::Map_t m_entities;
	Entity* m_selected;
	bool m_inRunningGameState;
	bool m_running;
	Pointer<ITask> m_timer;
	Pointer<ITask> m_physics;
public:
#pragma region Toolbox
	Pointer<GUIWindow> wndToolbox;
#pragma endregion
#pragma region PropertiesControls
	Pointer<GUIWindow> wndProperties;
	Pointer<GUIMenu> mnuEntityProperties;
	Pointer<GUITextbox> txtPositionX;
	Pointer<GUITextbox> txtPositionY;
	Pointer<GUITextbox> txtPositionZ;
	
	Pointer<GUIMenuItem> mitEntityWaypoint;	
	Pointer<GUITextbox> txtWaypointRadius;

	Pointer<GUIMenuItem> mitEntityPathfinder;	
	Pointer<GUITextbox> txtWaypointGroup;

	Pointer<GUIComboBox> cmbModelName;
	Pointer<GUITextbox> txtBodyPositionX;
	Pointer<GUITextbox> txtBodyPositionY;
	Pointer<GUITextbox> txtBodyPositionZ;
	Pointer<GUIComboBox> cmbRigidBodyTypes;
	Pointer<GUITextbox> txtEntityName;

	Pointer<GUIMenu> mnuLightProperties;
	Pointer<GUITextbox> txtLightPositionX;
	Pointer<GUITextbox> txtLightPositionY;
	Pointer<GUITextbox> txtLightPositionZ;

	Pointer<GUITextbox> txtLightAmbientR;
	Pointer<GUITextbox> txtLightAmbientG;
	Pointer<GUITextbox> txtLightAmbientB;
	
	Pointer<GUITextbox> txtLightDiffuseR;
	Pointer<GUITextbox> txtLightDiffuseG;
	Pointer<GUITextbox> txtLightDiffuseB;
	
	Pointer<GUITextbox> txtLightSpecularR;
	Pointer<GUITextbox> txtLightSpecularG;
	Pointer<GUITextbox> txtLightSpecularB;
#pragma endregion
#pragma region LoadModelControls
	Pointer<GUIWindow> wndLoadModel;
	Pointer<GUITextbox> txtModelFileName;
#pragma endregion
#pragma region CreateWaypointControls
	Pointer<GUIWindow> wndCreateWaypoint;
	Pointer<GUITextbox> txtWaypointGroupName;
#pragma endregion
#pragma region CreatePathfinderControls
	Pointer<GUIWindow> wndCreatePathfinder;
	Pointer<GUITextbox> txtWaypointName;
#pragma endregion
#pragma region CreateTerrainControls
	Pointer<GUIWindow> wndCreateTerrain;
	Pointer<GUITextbox> txtTerrainHeightmapFileName;
	Pointer<GUITextbox> txtTerrainName;
	Pointer<GUITextbox> txtTerrainPixelStep;
	Pointer<GUITextbox> txtTerrainTextures;
#pragma endregion
#pragma region RigidbodyDisplayControl
	Pointer<GUIWindow> wndRigidBodyDisplay;
	Pointer<GUIListBox> lstRigidBodyShapes;
	Pointer<GUIButton> btnRigidBodyDelete;
	Pointer<GUIButton> btnRigidBodyDeleteAll;
	Pointer<GUIButton> btnRigidBodyCancel;
#pragma endregion
#pragma region SceneGraphControls
	Pointer<GUIWindow> wndSceneGraphDisplay;
	Pointer<GUITree> treSceneGraphNodes;
#pragma endregion
#pragma region UnloadStateControls
	Pointer<GUIWindow> wndUnloadState;
	Pointer<GUITextbox> txtUnloadStateFileName;
#pragma endregion
#pragma region LoadStateControls
	Pointer<GUIWindow> wndLoadState;
	Pointer<GUITextbox> txtLoadStateFileName;
#pragma endregion
#pragma region EntityListWindow
	Pointer<GUIWindow> wndEntityList;
	Pointer<GUIListBox> lstEntityNames;
	Pointer<GUIButton> btnEntityDelete;
	Pointer<GUIButton> btnEntityDeleteCancel;
#pragma endregion
#pragma region LoadTextureControls
	Pointer<GUIWindow> wndLoadTexture;
	Pointer<GUITextbox> txtTextureFileName;
#pragma endregion
};